package com.wzl.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.wzl.dao.PatientInfoMapper;
import com.wzl.dao.TreatmentInfoMapper;
import com.wzl.entity.PatientNum;
import com.wzl.entity.PatientTree;
import com.wzl.entity.dto.PatientInfoDTO;
import com.wzl.entity.dto.TreatmentInfoDTO;
import com.wzl.entity.vo.PatientInfoVO;
import com.wzl.entity.vo.SysDictDataVO;
import com.wzl.responsitory.SelectCode;
import com.wzl.service.PatientInfoService;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import java.util.*;
import java.util.stream.Collectors;


@Service
public class PatientInfoServiceImpl extends ServiceImpl<PatientInfoMapper, PatientInfoDTO> implements PatientInfoService {

    @Autowired
    private SelectCode selectCode;

    @Autowired
    private PatientInfoMapper patientInfoMapper;

    @Autowired
    private TreatmentInfoMapper treatmentInfoMapper;

    @Override
    public Page<PatientInfoDTO> getPage(Page<PatientInfoDTO> page, PatientInfoDTO patientInfo) {
        QueryWrapper<PatientInfoDTO> queryWrapper = new QueryWrapper<>();
        if (StringUtils.isNotEmpty(patientInfo.getId())) {
            queryWrapper.lambda().like(PatientInfoDTO::getId, patientInfo.getId());
        }
        if (StringUtils.isNotEmpty(patientInfo.getName())) {
            queryWrapper.lambda().like(PatientInfoDTO::getName, patientInfo.getName());
        }
        Page<PatientInfoDTO> patientInfoDTOPage = this.baseMapper.selectPage(page, queryWrapper);
        conversion(patientInfoDTOPage.getRecords());
        return patientInfoDTOPage;
    }

    @Override
    public boolean savePatient(PatientInfoDTO patientInfo) {
        String startId = RandomStringUtils.randomAlphanumeric(6);
        int length = patientInfo.getIdCard().length();
        if (length < 6) {
            return false;
        }
        String endId = patientInfo.getIdCard().substring(length - 6, length);
        String belongAreaInfo = patientInfo.getBelongArea();
        StringBuilder stringBuffer = new StringBuilder();
        // 设置患者编号
        patientInfo.setId(stringBuffer.append(endId).append(startId).toString());
        // 设置治疗信息编号
        patientInfo.setTreatId(stringBuffer.append(belongAreaInfo).toString());
        return this.baseMapper.insert(patientInfo) > 0;
    }

    @Override
    public List<PatientInfoVO> getPatientInfo() {
        QueryWrapper<PatientInfoDTO> queryWrapper = new QueryWrapper<>();
        List<PatientInfoDTO> patientInfoList = this.baseMapper.selectList(queryWrapper);
        return patientInfoList.stream().map(data -> {
            PatientInfoVO patientInfoVO = new PatientInfoVO();
            patientInfoVO.setId(data.getId());
            patientInfoVO.setName(data.getName());
            return patientInfoVO;
        }).collect(Collectors.toList());
    }

    @Override
    public List<PatientNum> getPatientNum() {
        List<PatientNum> conNum = patientInfoMapper.getConNum();
        List<PatientNum> cureNum = patientInfoMapper.getCureNum();
        List<PatientNum> deathNum = patientInfoMapper.getDeathNum();
        List<PatientNum> list = conNum.stream().map(m -> {
            cureNum.stream().filter(m2 -> Objects.equals(m.getBelongArea(), m2.getBelongArea())).forEach(m2 -> {
                m.setCureNum(m2.getCureNum());
            });
            return m;
        }).collect(Collectors.toList());
        List<PatientNum> patientNumList = list.stream().map(m -> {
            deathNum.stream().filter(m2 -> Objects.equals(m.getBelongArea(), m2.getBelongArea())).forEach(m2 -> {
                m.setDeathNum(m2.getDeathNum());
            });
            return m;
        }).collect(Collectors.toList());
        return patientNumList;
    }

    @Override
    public List<PatientTree> optionTreeInfo() {
        List<String> codeListValue = Arrays.asList("countyArea");
        Map<String, List<SysDictDataVO>> stringListMap = selectCode.dealAllCode(codeListValue);
        List<SysDictDataVO> codeList = stringListMap.get("countyArea");
        List<PatientInfoDTO> patientInfoList = patientInfoMapper.listAllInfo();
        List<PatientNum> patientNums = patientInfoMapper.belongAreaNum();
        List<PatientTree> patientTreeList = new ArrayList<>();
        codeList.forEach(codeValue -> {
            PatientTree patientTree = new PatientTree();
            patientTree.setLabel(codeValue.getLabel());
            patientTree.setValue(codeValue.getValue());
            List<PatientTree> tempTreeList = new ArrayList<>();
            patientInfoList.forEach(patientInfo -> {
                if (StringUtils.equals(codeValue.getValue(), patientInfo.getBelongArea())) {
                    PatientTree tempTree = new PatientTree();
                    tempTree.setLabel(patientInfo.getName());
                    tempTree.setValue(patientInfo.getId());
                    tempTreeList.add(tempTree);
                }
            });
            patientTree.setChildren(tempTreeList);
            patientTreeList.add(patientTree);
        });
        for (PatientTree patientTree : patientTreeList) {
            for (PatientNum patientNum : patientNums) {
                if (StringUtils.equals(patientTree.getValue(), patientNum.getBelongArea())) {
                    patientTree.setCount(patientNum.getCountNum());
                    break;
                } else {
                    patientTree.setCount(0);
                }
            }
        }

        List<PatientTree> treeList = patientTreeList.stream().sorted((a, b) -> b.getCount().compareTo(a.getCount())).collect(Collectors.toList());
        return treeList;
    }

    @Override
    public PatientInfoDTO patientDetail(String id) {
        return this.baseMapper.selectById(id);
    }

    @Override
    public boolean deletePatient(String id) {
        boolean b = true;
        PatientInfoDTO patientInfoDTO = this.baseMapper.selectById(id);
        if (StringUtils.isNotEmpty(patientInfoDTO.getTreatId())) {
            List<TreatmentInfoDTO> byTreatList = this.treatmentInfoMapper.findByTreatId(patientInfoDTO.getTreatId());
            // 判断是否存在该治疗编号 该治疗编号是否存在治疗数据
            if (!CollectionUtils.isEmpty(byTreatList)) {
                b = treatmentInfoMapper.deleteByIds(patientInfoDTO.getTreatId());
            }
        }
        return this.baseMapper.deleteById(id) > 0 && b;
    }

    @Override
    public boolean updatePatient(PatientInfoDTO patientInfoDTO) {
        return this.baseMapper.updateById(patientInfoDTO) > 0;
    }

    private void conversion(List<PatientInfoDTO> info) {
        List<String> dicCode = Arrays.asList("sex", "countyArea", "patientState");
        Map<String, List<SysDictDataVO>> listMap = selectCode.dealAllCode(dicCode);
        info.forEach(data -> {
            for (SysDictDataVO sysDictDataVO : listMap.get("sex")) {
                if (StringUtils.equals(sysDictDataVO.getValue(), data.getSex())) {
                    data.setSex(sysDictDataVO.getLabel());
                    break;
                }
            }
            for (SysDictDataVO sysDictDataVO : listMap.get("countyArea")) {
                if (StringUtils.equals(sysDictDataVO.getValue(), data.getBelongArea())) {
                    data.setBelongArea(sysDictDataVO.getLabel());
                    break;
                }
            }
            for (SysDictDataVO sysDictDataVO : listMap.get("patientState")) {
                if (StringUtils.equals(sysDictDataVO.getValue(), data.getPatientState())) {
                    data.setPatientState(sysDictDataVO.getLabel());
                    break;
                }
            }
        });
    }
}
